#include "findautokeylenght.h"

#include <QHash>
#include <QtDebug>

FindAutokeyLenght::FindAutokeyLenght(QByteArray input, QByteArray alphabet, int maxLength, bool doXor, QObject *parent) :
    QThread(parent), input(input), alphabet(alphabet), maxLength(maxLength), doXor(doXor)
{}

QByteArray FindAutokeyLenght::vigenerize(QByteArray autokey, int keyLenght)
{
    QByteArray out;
    out.resize(autokey.length());
    for (int i = 0; i < keyLenght; i++)
        out[i] = autokey[i];
    if (doXor)
        for (int i = keyLenght; i < autokey.size(); i++)
            out[i] = autokey[i] ^ out[i - keyLenght];
    else
        for (int i = keyLenght; i < autokey.size(); i++)
            out [i] = autokey[i] - out[i - keyLenght];
    return out;
}

void FindAutokeyLenght::run()
{
    int size = input.size();

    QList<qreal> kappa_observed;
    kappa_observed << 0;

    for(int len = 1; len < maxLength; len++)
    {
        QByteArray vige = vigenerize(input, len);
        kappa_observed << 0;
        foreach (char c, alphabet) {
            int f = vige.count(c);
            kappa_observed[len] += f*(f-1);
        }
        kappa_observed[len] /= size*(size-1);
        qDebug() << len << "kappa_observed" << kappa_observed[len];
    }
    int len = 0;
    qreal kappa_max = 0;
    for (int i = 0; i < kappa_observed.size(); i++)
        if (kappa_observed[i] > kappa_max)
        {
            len = i;
            kappa_max = kappa_observed[i];
        }
    emit done(len);
}

//        QList<QHash<char, int> > counts;
//        counts.clear();
//        QList<qreal> ioc;
//        for (int i = 0; i < len; i++)
//        {
//            counts << QHash<char, int>();
//        }

//        for (int i = 0; i < size; i++)
//            counts[i % len][input[i]]++;

//        ioc.clear();
//        QHash<char, int> count;
//        foreach (count, counts)
//        {
//            qreal kappa_parziale = 0;
//            int somma = 0;
//            foreach (int f, count) {
//                kappa_parziale += f*(f-1);
//                somma += f;
//            }
//            kappa_parziale /= somma * (somma - 1);
//            ioc << kappa_parziale;
//        }
//        //media
//        qreal avg = 0;
//        foreach (qreal v, ioc) avg += v;
//        avg /= ioc.size();
//        qDebug() << len << "kappa_medio" << avg;

//        if (avg > (kappa_plaintext + kappa_random) / 2)
//        {
//            //success
//            emit done(len);
//            return;
//        }

////        emit done(len);
////    }
//    //fail
//    emit done(-1);
//}
